
#ifndef GameWindow_h
#define GameWindow_h

#include <Defines.h>
#include <CSharpPropertyMethods.h>

// Riccsson includes.
#include <System/Object.h>
#include <System/IntPtr.h>
#include <System/String.h>
#include <System/Generic/EventHandler.h>
#include <System/EventArgs.h>

// XNA includes.
#include "DisplayOrientation.h"
#include "Rectangle.h"

namespace Riccsson
{
	namespace Xna
	{
		namespace Framework
		{
			/*abstract*/ class GameWindow
				: public Riccsson::System::Object
			{
				#pragma region Properties

				PROP3(GameWindow, bool, AllowUserResizing)
				PROP3(GameWindow, Rectangle, ClientBounds)
				PROP3(GameWindow, DisplayOrientation, CurrentOrientation)
				PROP3(GameWindow, Riccsson::System::IntPtr, Handle)
				PROP3(GameWindow, GC_PTR<Riccsson::System::string>, ScreenDeviceName)
				PROP3(GameWindow, GC_PTR<Riccsson::System::string>, Title)
				PROP3(GameWindow, bool, IsBorderless)

				//[DefaultValue(false)]
				public: virtual PROP3_GET(bool, AllowUserResizing) = 0; // { get; set; }
				public: virtual PROP3_SET(bool, AllowUserResizing) = 0; // { get; set; }
						
				public: virtual PROP3_GET(Rectangle, ClientBounds) = 0;
				private: PROP3_SET(Rectangle, ClientBounds){throw;}

				public: virtual PROP3_GET(DisplayOrientation, CurrentOrientation) = 0;
				private: PROP3_SET(DisplayOrientation, CurrentOrientation){throw;}

				public: virtual PROP3_GET(Riccsson::System::IntPtr, Handle) = 0;
				private: PROP3_SET(Riccsson::System::IntPtr, Handle){throw;}

				public: virtual PROP3_GET(GC_PTR<Riccsson::System::string>, ScreenDeviceName) = 0;
				private: PROP3_SET(GC_PTR<Riccsson::System::string>, ScreenDeviceName){throw;}

				private: GC_PTR<Riccsson::System::string> _title;
				public: PROP3_GET(GC_PTR<Riccsson::System::string>, Title)
				{
					return _title; 
				}
				public: PROP3_SET(GC_PTR<Riccsson::System::string>, Title)
				{
					if (_title != value)
					{
						SetTitle(value);
						_title = value;
					}
				}

				/// <summary>
				/// Determines whether the border of the window is visible. Currently only supported on the WinDX and WinGL/Linux platforms.
				/// </summary>
				/// <exception cref="System.NotImplementedException">
				/// Thrown when trying to use this property on a platform other than the WinDX and WinGL/Linux platforms.
				/// </exception>
				public: virtual PROP3_GET(bool, IsBorderless)
				{
					return false;
				}
				public: virtual PROP3_SET(bool, IsBorderless)
				{
					throw Riccsson::System::NotImplementedException();
				}

				#pragma endregion Properties

				#pragma region Events

				public: event<Void, Riccsson::System::Generic::EventHandler<Riccsson::System::EventArgs>> ClientSizeChanged;
				public: event<Void, Riccsson::System::Generic::EventHandler<Riccsson::System::EventArgs>> OrientationChanged;
				public: event<Void, Riccsson::System::Generic::EventHandler<Riccsson::System::EventArgs>> ScreenDeviceNameChanged;

				#pragma endregion Events

				public: virtual void BeginScreenDeviceChange (bool willBeFullScreen) = 0;

				public: virtual void EndScreenDeviceChange (GC_PTR<Riccsson::System::string> screenDeviceName, int clientWidth, int clientHeight) = 0;

				public: void EndScreenDeviceChange (GC_PTR<Riccsson::System::string> screenDeviceName)
				{
					EndScreenDeviceChange(screenDeviceName, ClientBounds.get().Width, ClientBounds.get().Height);
				}

				protected: void OnActivated ()
				{
				}

				protected: void OnClientSizeChanged ()
				{
					if (ClientSizeChanged != null)
						ClientSizeChanged (this, Riccsson::System::EventArgs::Empty);
				}

				protected: void OnDeactivated ()
				{
				}
         
				protected: void OnOrientationChanged ()
				{
					if (OrientationChanged != null)
						OrientationChanged (this, Riccsson::System::EventArgs::Empty);
				}

				protected: void OnPaint ()
				{
				}

				protected: void OnScreenDeviceNameChanged ()
				{
					if (ScreenDeviceNameChanged != null)
						ScreenDeviceNameChanged (this, Riccsson::System::EventArgs::Empty);
				}

				protected: /*internal*/ virtual void SetSupportedOrientations (DisplayOrientation orientations) = 0;
				protected: virtual void SetTitle (GC_PTR<Riccsson::System::string> title) = 0;
			};
		}
	}
}

#endif